package com.zzb.framework.utils;

import com.alibaba.fastjson.JSON;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.reflect.FieldUtils;
import org.joda.time.DateTime;
import org.joda.time.format.DateTimeFormat;
import org.joda.time.format.DateTimeFormatter;
import org.springframework.util.DigestUtils;

import javax.imageio.ImageIO;
import javax.servlet.http.HttpServletRequest;
import java.awt.image.BufferedImage;
import java.io.IOException;
import java.io.InputStream;
import java.lang.reflect.Field;
import java.math.BigDecimal;
import java.text.DecimalFormat;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * 工具类
 * Created by zzb on 15/12/30.
 */
public class Misc {
    public static boolean toBoolean(String s ){
        return "true".equals(StringUtils.trim(s)) || "1".equals(StringUtils.trim(s));
    }
    public static boolean isZero(Long i){
        return i== null || i.equals(0L);
    }
    public static boolean isZero(Integer i){
        return i== null || i.equals(0);
    }
    public static boolean isZero(Float f){
        return f == null || f.equals(0f);
    }
    public static boolean isZero(Double d){
        return d == null || d.equals(0d);
    }
    public static boolean isZero(BigDecimal d){return d==null || d.compareTo(BigDecimal.ZERO)==0;}
    public static boolean isNotZero(Integer i){
        return !isZero(i);
    }
    public static boolean isNotZero(Float f){
        return ! isZero(f);
    }
    public static boolean isNotZero(Double d){
        return ! isZero(d);
    }
    public static boolean isNotZero(BigDecimal d){
        return ! isZero(d);
    }
    public static boolean isTrue(Boolean b){return null!=b&&b;}
    public static boolean isFalse(Boolean b){return !isTrue(b);}
    public static int toPrimitive(Integer value ,int defaultValue){return value==null?defaultValue:value;}
    public static float toPrimitive(Float value ,float defaultValue){return value==null?defaultValue:value;}
    public static double toPrimitive(Double value ,double defaultValue){return value==null?defaultValue:value;}
    public static char toPrimitive(Character value ,char defaultValue){return value==null?defaultValue:value;}
    public static boolean toPrimitive(Boolean value ,boolean defaultValue){return value==null?defaultValue:value;}
    public static short toPrimitive(Short value ,short defaultValue){return value==null?defaultValue:value;}
    public static boolean isNumber(String str){ try { long l = Long.parseLong(str); } catch (NumberFormatException e) { return false; } return true; }
    public static boolean isNotNumber(String str){ return !isNumber(str);}
    public static int compare(BigDecimal d1,BigDecimal d2){
        if(d1 == null)return -1;
        if(d2 == null) return 1;
        if(d1.doubleValue() == d2.doubleValue()) return 0;
        if(d1.doubleValue() > d2.doubleValue()) return 1;
        if(d1.doubleValue() < d2.doubleValue()) return -1;
        return 0;
    }
    static int index = 1;
    /**基于时间生成唯一表示，可以用来代替UUID，但同一毫秒不能超过999条*/
    public static Long generateTimeKeyLong(){
        return Long.parseLong(generateTimeKey());
    }
    public static synchronized String generateTimeKey(){
        if(index == 999){
            index = 1;
        }
        DecimalFormat df = new DecimalFormat("000");
        return DateTime.now().getMillis() + "" + df.format(index++);
    }
    /**获取随机字符串*/
    public static String getRandomString(int length) { //length表示生成字符串的长度
        String base = "abcdefghijkmnpqrstuvwxyz23456789";
        Random random = new Random();
        StringBuffer sb = new StringBuffer();
        for (int i = 0; i < length; i++) {
            int number = random.nextInt(base.length());
            sb.append(base.charAt(number));
        }
        return sb.toString();
    }

    /**获取图片信息*/
    public static Map<String ,Integer> imageInfo(InputStream is){
        Map<String,Integer > imageInfoMap = new HashMap<>();
        try {
            BufferedImage bufferedImage = ImageIO.read(is);
            int width = bufferedImage.getWidth();
            int height = bufferedImage.getHeight();
            imageInfoMap.put("h",height);
            imageInfoMap.put("w",width);
        } catch (IOException e) {
            //TODO
            imageInfoMap.put("h",500);
            imageInfoMap.put("w",500);
        }
        return imageInfoMap;
    }
    /**判断是不是手机号码*/
    public static boolean isMobilephone(String mobilephone){
        if(StringUtils.isBlank(mobilephone)) return false;
        String reg = "^1(3[0-9]|4[0-9]|5[0-9]|7[0-9]|8[0-9])\\d{8}$";
        Pattern pattern = Pattern.compile(reg);
        Matcher matcher = pattern.matcher(mobilephone);
        return matcher.find();
    }
    /**是否是手机号或座机*/
    public static boolean isPhone(String phone){
        if(StringUtils.isBlank(phone)) return false;
        String reg = "^(0|86|17951)?(13[0-9]|15[0-9]|17[0-9]|18[0-9]|14[0-9])[0-9]{8}$";
        Pattern pattern = Pattern.compile(reg);
        Matcher matcher = pattern.matcher(phone);
        return matcher.find();

    }
    /**判断字符串是不是汉字*/
    public static boolean isChinese(String str){
        if(StringUtils.isBlank(str))return false;
        for (int i = 0; i < str.length(); i++) {
            char c = str.charAt(i);
            if (!isChineseChar(c))return false;
        }
        return true;
    }
    /**判断字符是不是汉字*/
    public static boolean isChineseChar(char oneChar){
        return (oneChar >= '\u4e00' && oneChar <= '\u9fa5')
                || (oneChar >= '\uf900' && oneChar <= '\ufa2d');
    }

    /**是否是身份证*/
    public static boolean isIdCard(String idCard){
        if(StringUtils.isBlank(idCard))return false;
        String reg = "^((11|12|13|14|15|21|22|23|31|32|33|34|35|36|37|41|42|43|44|45|46|50|51|52|53|54|61|62|63|64|65|71|81|82|91)\\d{4})((((19|20)(([02468][048])|([13579][26]))0229))|((20[0-9][0-9])|(19[0-9][0-9]))((((0[1-9])|(1[0-2]))((0[1-9])|(1\\d)|(2[0-8])))|((((0[1,3-9])|(1[0-2]))(29|30))|(((0[13578])|(1[02]))31))))((\\d{3}(x|X))|(\\d{4}))$";
        Pattern pattern = Pattern.compile(reg);
        Matcher matcher = pattern.matcher(idCard);
        return matcher.find();
    }
    /**判断是否是澳门的身份证*/
    public static boolean isAoMenIdCard(String idCard){
        if(StringUtils.isBlank(idCard))return false;
        String reg = "^[1|5|7][0-9]{6}\\([0-9Aa]\\)$";
        Pattern pattern = Pattern.compile(reg);
        Matcher matcher = pattern.matcher(idCard);
        return matcher.find();
    }

    /**判断是否是台湾的身份证*/
    public static boolean isTaiWanIdCard(String idCard){
        if(StringUtils.isBlank(idCard))return false;
        String reg = "^[A-Z][0-9]{9}$";
        Pattern pattern = Pattern.compile(reg);
        Matcher matcher = pattern.matcher(idCard);
        return matcher.find();
    }

    /**判断是否是香港的身份证*/
    public static boolean isXiangGangIdCard(String idCard){
        if(StringUtils.isBlank(idCard))return false;
        String reg = "^[A-Z][0-9]{6}\\([0-9A]\\)$";
        Pattern pattern = Pattern.compile(reg);
        Matcher matcher = pattern.matcher(idCard);
        return matcher.find();
    }


    /**获取当前域名*/
    public static String getDomainName(HttpServletRequest request){
        StringBuilder domainName = new StringBuilder();
        String serverName = request.getServerName();
        String scheme = request.getScheme();
        domainName.append(scheme).append("://").append(serverName);
        int serverPort = request.getServerPort();
        if(serverPort != 80){
            domainName.append(":").append(serverPort);
        }
        return domainName.toString();
    }

    public static void main(String[] args) {
        DateTimeFormatter format = DateTimeFormat.forPattern("yyyy-MM-dd HH:mm:ss");
        DateTime dateTime = DateTime.parse("2016-10-29 22:00:00",format);
    }

    /**将一个列表更具某个属性分组*/
    public static <T> Map<String,List<T>> parseToStringKeyMap(List<T> entities, String propertyName) throws Exception{
        final Map<String,List<T>> map = new HashMap<>();
        if(CollectionUtils.isNotEmpty(entities))
        for (T t : entities) {
            Field field = ReflectionUtils.getAllDeclaredField(entities.get(0).getClass(), propertyName);
            if(!field.getType().equals(String.class)) throw new Exception("所选分类属性类型必须是String");
            Object propertyValue = FieldUtils.readDeclaredField(t, propertyName, true);
            if(propertyValue == null) continue;
            String propertyStringValue = (String) propertyValue;

            if(!map.containsKey(propertyStringValue)){
                map.put(propertyStringValue,new ArrayList<>());
            }

            map.get(propertyStringValue).add(t);
        }
        return map;
    }

}
